< Summary

Class:GDX.Collections.SparseSet
Assembly:GDX
File(s):D:/BuildAgent/work/GDX-Documentation/Projects/GDX_Development/Packages/com.dotbunny.gdx/GDX/Collections/SparseSet.cs
Covered lines:365
Uncovered lines:695
Coverable lines:1060
Total lines:1825
Line coverage:34.4% (365 of 1060)
Covered branches:0
Total branches:0
Covered methods:25
Total methods:51
Method coverage:49% (25 of 51)

Coverage History

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity NPath complexity Sequence coverage
SparseSet(...)0%220100%
SparseSet(...)0%220100%
AddWithExpandCheck(...)0%330100%
AddWithExpandCheck(...)0%12300%
AddUnchecked(...)0%110100%
AddUnchecked(...)0%110100%
GetDenseIndexUnchecked(...)0%110100%
GetDenseIndexWithBoundsCheck(...)0%6.016092.86%
GetDenseIndexWithVersionCheck(...)0%220100%
GetDenseIndexWithBoundsAndVersionCheck(...)0%7.017093.33%
RemoveWithBoundsCheck(...)0%770100%
RemoveWithVersionCheck(...)0%220100%
RemoveWithBoundsAndVersionChecks(...)0%880100%
RemoveUnchecked(...)0%110100%
RemoveUnchecked(...)0%110100%
RemoveUnchecked(...)0%110100%
RemoveUncheckedFromDenseIndex(...)0%110100%
RemoveUncheckedFromDenseIndex(...)0%110100%
RemoveUncheckedFromDenseIndex(...)0%110100%
RemoveUncheckedFromDenseIndex(...)0%110100%
Clear()0%220100%
Clear(...)0%220100%
ClearWithVersionArrayReset(...)0%220100%
Expand(...)0%220100%
Expand(...)0%220100%
Reserve(...)0%330100%
Reserve(...)0%12300%
AddWithExpandCheck[T0](...)0%12300%
AddWithExpandCheck[T0, T1](...)0%12300%
AddWithExpandCheck[T0, T1, T2](...)0%12300%
AddWithExpandCheck[T0, T1, T2, T3](...)0%12300%
AddWithExpandCheck[T0, T1, T2, T3, T4](...)0%12300%
AddWithExpandCheck[T0, T1, T2, T3, T4, T5](...)0%12300%
AddWithExpandCheck[T0, T1, T2, T3, T4, T5, T6](...)0%12300%
AddWithExpandCheck[T0, T1, T2, T3, T4, T5, T6, T7](...)0%12300%
AddUnchecked[T0](...)0%2100%
AddUnchecked[T0, T1](...)0%2100%
AddUnchecked[T0, T1, T2](...)0%2100%
AddUnchecked[T0, T1, T2, T3](...)0%2100%
AddUnchecked[T0, T1, T2, T3, T4](...)0%2100%
AddUnchecked[T0, T1, T2, T3, T4, T5](...)0%2100%
AddUnchecked[T0, T1, T2, T3, T4, T5, T6](...)0%2100%
AddUnchecked[T0, T1, T2, T3, T4, T5, T6, T7](...)0%2100%
RemoveUnchecked[T0](...)0%2100%
RemoveUnchecked[T0, T1](...)0%2100%
RemoveUnchecked[T0, T1, T2](...)0%2100%
RemoveUnchecked[T0, T1, T2, T3](...)0%2100%
RemoveUnchecked[T0, T1, T2, T3, T4](...)0%2100%
RemoveUnchecked[T0, T1, T2, T3, T4, T5](...)0%2100%
RemoveUnchecked[T0, T1, T2, T3, T4, T5, T6](...)0%2100%
RemoveUnchecked[T0, T1, T2, T3, T4, T5, T6, T7](...)0%2100%

File(s)

D:/BuildAgent/work/GDX-Documentation/Projects/GDX_Development/Packages/com.dotbunny.gdx/GDX/Collections/SparseSet.cs

#LineLine coverage
 1// Copyright (c) 2020-2023 dotBunny Inc.
 2// dotBunny licenses this file to you under the BSL-1.0 license.
 3// See the LICENSE file in the project root for more information.
 4
 5using System;
 6using System.Runtime.CompilerServices;
 7
 8namespace GDX.Collections
 9{
 10    /// <summary>
 11    ///     An adapter collection for external data arrays that allows constant-time insertion, deletion, and lookup by
 12    ///     handle, as well as array-like iteration.
 13    /// </summary>
 14    public struct SparseSet
 15    {
 16        /// <summary>
 17        ///     Holds references to the sparse array for swapping indices.
 18        /// </summary>
 19        public int[] DenseArray;
 20
 21        /// <summary>
 22        ///     Holds references to dense array indices.
 23        /// </summary>
 24        /// <remarks>
 25        ///     Its own indices are claimed and freed via a free-list.
 26        /// </remarks>
 27        public int[] SparseArray;
 28
 29        /// <summary>
 30        ///     How many indices are being used currently?
 31        /// </summary>
 32        public int Count;
 33
 34        /// <summary>
 35        ///     The first free (currently unused) index in the sparse array.
 36        /// </summary>
 37        public int FreeIndex;
 38
 39        /// <summary>
 40        ///     Create a <see cref="SparseSet" /> with an <paramref name="initialCapacity" />.
 41        /// </summary>
 42        /// <param name="initialCapacity">The initial capacity of the sparse and dense int arrays.</param>
 43        public SparseSet(int initialCapacity)
 3844        {
 3845            DenseArray = new int[initialCapacity];
 3846            SparseArray = new int[initialCapacity];
 3847            Count = 0;
 3848            FreeIndex = 0;
 49
 22850            for (int i = 0; i < initialCapacity; i++)
 7651            {
 7652                DenseArray[i] = -1;
 7653                SparseArray[i] = i + 1;
 7654            }
 3855        }
 56
 57        /// <summary>
 58        ///     Create a <see cref="SparseSet" /> with an <paramref name="initialCapacity" />.
 59        /// </summary>
 60        /// <param name="initialCapacity">The initial capacity of the sparse and dense int arrays.</param>
 61        /// <param name="versionArray">Array containing version numbers to check sparse references against.</param>
 62        public SparseSet(int initialCapacity, out ulong[] versionArray)
 1663        {
 1664            DenseArray = new int[initialCapacity];
 1665            SparseArray = new int[initialCapacity];
 1666            versionArray = new ulong[initialCapacity];
 1667            Count = 0;
 1668            FreeIndex = 0;
 69
 11670            for (int i = 0; i < initialCapacity; i++)
 4271            {
 4272                DenseArray[i] = -1;
 4273                SparseArray[i] = i + 1;
 4274                versionArray[i] = 1;
 4275            }
 1676        }
 77
 78        /// <summary>
 79        ///     Adds a sparse/dense index pair to the set and expands the arrays if necessary.
 80        /// </summary>
 81        /// <param name="expandBy">How many indices to expand by.</param>
 82        /// <param name="sparseIndex">The sparse index allocated.</param>
 83        /// <param name="denseIndex">The dense index allocated.</param>
 84        /// <returns>True if the index pool expanded.</returns>
 85        public bool AddWithExpandCheck(int expandBy, out int sparseIndex, out int denseIndex)
 686        {
 687            int indexToClaim = FreeIndex;
 688            int currentCapacity = SparseArray.Length;
 689            bool needsExpansion = false;
 90
 691            if (indexToClaim >= currentCapacity)
 392            {
 93                // We're out of space, the last free index points to nothing. Allocate more indices.
 394                needsExpansion = true;
 95
 396                int newCapacity = currentCapacity + expandBy;
 97
 398                int[] newSparseArray = new int[newCapacity];
 399                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 3100                SparseArray = newSparseArray;
 101
 3102                int[] newDenseArray = new int[newCapacity];
 3103                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 3104                DenseArray = newDenseArray;
 105
 36106                for (int i = currentCapacity; i < newCapacity; i++)
 15107                {
 15108                    SparseArray[i] = i + 1; // Build the free list chain.
 15109                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 15110                }
 3111            }
 112
 6113            int nextFreeIndex = SparseArray[indexToClaim];
 6114            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 6115            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 6116            denseIndex = Count;
 117
 6118            ++Count;
 6119            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 120
 6121            sparseIndex = indexToClaim;
 6122            return needsExpansion;
 6123        }
 124
 125        /// <summary>
 126        ///     Adds a sparse/dense index pair to the set and expands the arrays if necessary.
 127        /// </summary>
 128        /// <param name="expandBy">How many indices to expand by.</param>
 129        /// <param name="sparseIndex">The sparse index allocated.</param>
 130        /// <param name="denseIndex">The dense index allocated.</param>
 131        /// <param name="versionArray">The array containing the version number to check against.</param>
 132        /// <param name="version">Enables detection of use-after-free errors when using the sparse index as a reference.
 133        /// <returns>True if the index pool expanded.</returns>
 134        public bool AddWithExpandCheck(int expandBy, out int sparseIndex, out int denseIndex, ref ulong[] versionArray, 
 0135        {
 0136            int indexToClaim = FreeIndex;
 0137            int currentCapacity = SparseArray.Length;
 0138            bool needsExpansion = false;
 139
 0140            if (indexToClaim >= currentCapacity)
 0141            {
 142                // We're out of space, the last free index points to nothing. Allocate more indices.
 0143                needsExpansion = true;
 144
 0145                int newCapacity = currentCapacity + expandBy;
 146
 0147                int[] newSparseArray = new int[newCapacity];
 0148                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 0149                SparseArray = newSparseArray;
 150
 0151                int[] newDenseArray = new int[newCapacity];
 0152                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 0153                DenseArray = newDenseArray;
 154
 0155                ulong[] newVersionArray = new ulong[newCapacity];
 0156                Array.Copy(versionArray, 0, newVersionArray, 0, currentCapacity);
 0157                versionArray = newVersionArray;
 158
 0159                for (int i = currentCapacity; i < newCapacity; i++)
 0160                {
 0161                    SparseArray[i] = i + 1; // Build the free list chain.
 0162                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 0163                    newVersionArray[i] = 1;
 0164                }
 0165            }
 166
 0167            int nextFreeIndex = SparseArray[indexToClaim];
 0168            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 0169            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 0170            denseIndex = Count;
 171
 0172            version = versionArray[indexToClaim];
 173
 0174            ++Count;
 0175            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 176
 0177            sparseIndex = indexToClaim;
 0178            return needsExpansion;
 0179        }
 180
 181        /// <summary>
 182        ///     Adds a sparse/dense index pair to the set without checking if the set needs to expand.
 183        /// </summary>
 184        /// <param name="sparseIndex">The sparse index allocated.</param>
 185        /// <param name="denseIndex">The dense index allocated.</param>
 186        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 187        public void AddUnchecked(out int sparseIndex, out int denseIndex)
 20188        {
 20189            int indexToClaim = FreeIndex;
 20190            int nextFreeIndex = SparseArray[indexToClaim];
 19191            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 19192            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 193
 19194            sparseIndex = indexToClaim;
 19195            denseIndex = Count;
 19196            ++Count;
 19197            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 19198        }
 199
 200        /// <summary>
 201        ///     Adds a sparse/dense index pair to the set without checking if the set needs to expand.
 202        /// </summary>
 203        /// <param name="sparseIndex">The sparse index allocated.</param>
 204        /// <param name="denseIndex">The dense index allocated.</param>
 205        /// <param name="versionArray">The array containing the version number to check against.</param>
 206        /// <param name="version">Enables detection of use-after-free errors when using the sparse index as a reference.
 207        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 208        public void AddUnchecked(out int sparseIndex, out int denseIndex, ulong[] versionArray, out ulong version)
 24209        {
 24210            int indexToClaim = FreeIndex;
 24211            int nextFreeIndex = SparseArray[indexToClaim];
 23212            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 23213            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 214
 23215            version = versionArray[indexToClaim];
 23216            sparseIndex = indexToClaim;
 23217            denseIndex = Count;
 218
 23219            ++Count;
 23220            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 23221        }
 222
 223        /// <summary>
 224        ///     Gets the value of the sparse array at the given index without any data validation.
 225        /// </summary>
 226        /// <param name="sparseIndex">The index to check in the sparse array.</param>
 227        /// <returns>The dense index at the given sparse index.</returns>
 228        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 229        public int GetDenseIndexUnchecked(int sparseIndex)
 1230        {
 1231            return SparseArray[sparseIndex];
 1232        }
 233
 234        /// <summary>
 235        ///     Gets the value of the sparse array at the given index,
 236        ///     or -1 if the dense and sparse indices don't point to each other or if the dense index is outside the den
 237        /// </summary>
 238        /// <param name="sparseIndex">The index in the sparse array to check against.</param>
 239        /// <returns>The dense index pointed to by the current sparse index, or -1 if invalid.</returns>
 240        public int GetDenseIndexWithBoundsCheck(int sparseIndex)
 4241        {
 4242            if (sparseIndex >= 0 && sparseIndex < SparseArray.Length)
 2243            {
 2244                int denseIndex = SparseArray[sparseIndex];
 245
 2246                if (denseIndex < Count && denseIndex >= 0)
 1247                {
 1248                    int sparseIndexAtDenseIndex = DenseArray[denseIndex];
 249
 1250                    if (sparseIndex == sparseIndexAtDenseIndex)
 1251                    {
 1252                        return denseIndex;
 253                    }
 0254                }
 1255            }
 256
 3257            return -1;
 4258        }
 259
 260        /// <summary>
 261        ///     Gets the value of the sparse array at the given index,
 262        ///     or -1 if the version number does not match.
 263        /// </summary>
 264        /// <param name="sparseIndex">The index in the sparse array to check against.</param>
 265        /// <param name="version">The version number associated with the sparse index.</param>
 266        /// <param name="versionArray">The array containing the version number to check against.</param>
 267        /// <returns>The dense index pointed to by the current sparse index, or -1 if invalid.</returns>
 268        public int GetDenseIndexWithVersionCheck(int sparseIndex, ulong version, ulong[] versionArray)
 4269        {
 4270            int denseIndex = SparseArray[sparseIndex];
 4271            ulong versionAtSparseIndex = versionArray[sparseIndex];
 272
 4273            if (version == versionAtSparseIndex)
 2274            {
 2275                return denseIndex;
 276            }
 277
 2278            return -1;
 4279        }
 280
 281        /// <summary>
 282        ///     Gets the value of the sparse array at the given index,
 283        ///     or -1 if the given sparse index is invalid..
 284        /// </summary>
 285        /// <param name="sparseIndex">The index in the sparse array to check against.</param>
 286        /// <param name="version">The version number associated with the sparse index.</param>
 287        /// <param name="versionArray">The array containing the version number to check against.</param>
 288        /// <returns>The dense index pointed to by the current sparse index, or -1 if invalid.</returns>
 289        public int GetDenseIndexWithBoundsAndVersionCheck(int sparseIndex, ulong version, ulong[] versionArray)
 7290        {
 7291            if (sparseIndex >= 0 && sparseIndex < SparseArray.Length)
 5292            {
 5293                int denseIndex = SparseArray[sparseIndex];
 5294                ulong versionAtSparseIndex = versionArray[sparseIndex];
 295
 5296                if (versionAtSparseIndex == version && denseIndex < Count && denseIndex >= 0)
 2297                {
 2298                    int sparseIndexAtDenseIndex = DenseArray[denseIndex];
 299
 2300                    if (sparseIndex == sparseIndexAtDenseIndex)
 2301                    {
 2302                        return denseIndex;
 303                    }
 0304                }
 3305            }
 306
 5307            return -1;
 7308        }
 309
 310        /// <summary>
 311        ///     Frees the allocated entry corresponding to the sparse index.
 312        ///     WARNING: Will not protect against accidentally removing twice if the index in question was recycled betw
 313        /// <param name="sparseIndexToRemove">The sparse index corresponding to the entry to remove.</param>
 314        /// <param name="dataIndexToSwapTo">Replace the data array value at this index with the data array value at inde
 315        /// <param name="dataIndexToSwapFrom">
 316        ///     Set the data array value at this index to default after swapping with the data array
 317        ///     value at dataIndexToSwapTo.
 318        /// </param>
 319        /// </summary>
 320        /// <returns>True if the entry was valid and thus removed.</returns>
 321        public bool RemoveWithBoundsCheck(ref int sparseIndexToRemove, out int dataIndexToSwapFrom, out int dataIndexToS
 4322        {
 4323            dataIndexToSwapFrom = -1;
 4324            dataIndexToSwapTo = -1;
 4325            bool didRemove = false;
 4326            if (sparseIndexToRemove >= 0 && sparseIndexToRemove < SparseArray.Length)
 2327            {
 2328                int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 329
 2330                if (denseIndexToRemove >= 0 && denseIndexToRemove < Count)
 1331                {
 1332                    int sparseIndexAtDenseIndex = DenseArray[denseIndexToRemove];
 1333                    int newLength = Count - 1;
 1334                    int sparseIndexBeingSwapped = DenseArray[newLength];
 335
 1336                    if (denseIndexToRemove < Count && sparseIndexAtDenseIndex == sparseIndexToRemove)
 1337                    {
 1338                        didRemove = true;
 339                        // Swap the entry being removed with the last entry.
 1340                        SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 1341                        DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 342
 1343                        dataIndexToSwapFrom = newLength;
 1344                        dataIndexToSwapTo = denseIndexToRemove;
 345
 346                        // Clear the dense index, for debugging purposes
 1347                        DenseArray[newLength] = -1;
 348
 349                        // Add the sparse index to the free list.
 1350                        SparseArray[sparseIndexToRemove] = FreeIndex;
 1351                        FreeIndex = sparseIndexToRemove;
 352
 1353                        Count = newLength;
 1354                    }
 1355                }
 2356            }
 357
 4358            sparseIndexToRemove = -1;
 359
 4360            return didRemove;
 4361        }
 362
 363        /// <summary>
 364        ///     Removes the allocated entry corresponding to the sparse index.
 365        ///     Indicates which dense indices were swapped as a result of removing the entry.
 366        /// </summary>
 367        /// <param name="sparseIndexToRemove">The sparse index to remove.</param>
 368        /// <param name="version">
 369        ///     The version number of the int used to access the sparse index. Used to guard against accessing
 370        ///     indices that have been removed and reused.
 371        /// </param>
 372        /// <param name="versionArray">The array where version numbers to check against are stored.</param>
 373        /// <param name="dataIndexToSwapTo">Replace the data array value at this index with the data array value at inde
 374        /// <param name="dataIndexToSwapFrom">
 375        ///     Set the data array value at this index to default after swapping with the data array
 376        ///     value at dataIndexToSwapTo.
 377        /// </param>
 378        /// <returns>Whether or not the remove attempt succeeded.</returns>
 379        public bool RemoveWithVersionCheck(int sparseIndexToRemove, ulong version, ulong[] versionArray,
 380            out int dataIndexToSwapFrom, out int dataIndexToSwapTo)
 2381        {
 2382            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 2383            ulong versionAtSparseIndex = versionArray[sparseIndexToRemove];
 384
 2385            dataIndexToSwapFrom = -1;
 2386            dataIndexToSwapTo = -1;
 387
 2388            bool succeeded = versionAtSparseIndex == version;
 389
 2390            if (succeeded)
 1391            {
 1392                int newLength = Count - 1;
 1393                int sparseIndexBeingSwapped = DenseArray[newLength];
 394
 395                // Swap the entry being removed with the last entry.
 1396                SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 1397                DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 398
 399                // Clear the dense  index, for debugging purposes
 1400                DenseArray[newLength] = -1;
 401
 402                // Add the sparse index to the free list.
 1403                SparseArray[sparseIndexToRemove] = FreeIndex;
 1404                versionArray[sparseIndexToRemove] = versionArray[sparseIndexToRemove] + 1;
 1405                FreeIndex = sparseIndexToRemove;
 406
 1407                Count = newLength;
 408
 1409                dataIndexToSwapTo = denseIndexToRemove;
 1410                dataIndexToSwapFrom = newLength;
 1411            }
 412
 2413            return succeeded;
 2414        }
 415
 416        /// <summary>
 417        ///     Removes the allocated entry corresponding to the sparse index.
 418        /// </summary>
 419        /// <param name="sparseIndexToRemove">The sparse index corresponding to the entry to remove.</param>
 420        /// <param name="version">
 421        ///     The version number of the int used to access the sparse index. Used to guard against erroneously accessi
 422        ///     freed indices currently in use with an outdated reference.
 423        /// </param>
 424        /// <param name="dataIndexToSwapTo">Replace the data array value at this index with the data array value at inde
 425        /// <param name="dataIndexToSwapFrom">
 426        ///     Set the data array value at this index to default after swapping with the data array
 427        ///     value at dataIndexToSwapTo.
 428        /// </param>
 429        /// <param name="versionArray">The array where version numbers to check against are stored.</param>
 430        /// <returns>True if the entry was valid and thus removed.</returns>
 431        public bool RemoveWithBoundsAndVersionChecks(ref int sparseIndexToRemove, ulong version,
 432            ulong[] versionArray, out int dataIndexToSwapFrom, out int dataIndexToSwapTo)
 6433        {
 6434            dataIndexToSwapFrom = -1;
 6435            dataIndexToSwapTo = -1;
 6436            bool didRemove = false;
 6437            if (sparseIndexToRemove >= 0 && sparseIndexToRemove < SparseArray.Length)
 3438            {
 3439                ulong sparseIndexVersion = versionArray[sparseIndexToRemove];
 3440                int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 441
 3442                if (sparseIndexVersion == version && denseIndexToRemove >= 0 && denseIndexToRemove < Count)
 2443                {
 2444                    int sparseIndexAtDenseIndex = DenseArray[denseIndexToRemove];
 2445                    int newLength = Count - 1;
 2446                    int sparseIndexBeingSwapped = DenseArray[newLength];
 447
 2448                    if (denseIndexToRemove < Count && sparseIndexAtDenseIndex == sparseIndexToRemove)
 2449                    {
 2450                        didRemove = true;
 2451                        versionArray[sparseIndexToRemove] = sparseIndexVersion + 1;
 452                        // Swap the entry being removed with the last entry.
 2453                        SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 2454                        DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 455
 2456                        dataIndexToSwapFrom = newLength;
 2457                        dataIndexToSwapTo = denseIndexToRemove;
 458
 459                        // Clear the dense index, for debugging purposes
 2460                        DenseArray[newLength] = -1;
 461
 462                        // Add the sparse index to the free list.
 2463                        SparseArray[sparseIndexToRemove] = FreeIndex;
 2464                        FreeIndex = sparseIndexToRemove;
 465
 2466                        Count = newLength;
 2467                    }
 2468                }
 3469            }
 470
 6471            sparseIndexToRemove = -1;
 472
 6473            return didRemove;
 6474        }
 475
 476        /// <summary>
 477        ///     Removes the associated sparse/dense index pair from active use.
 478        /// </summary>
 479        /// <param name="sparseIndexToRemove">The sparse index to remove.</param>
 480        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 481        public void RemoveUnchecked(int sparseIndexToRemove)
 1482        {
 1483            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 1484            int newLength = Count - 1;
 1485            int sparseIndexBeingSwapped = DenseArray[newLength];
 486
 487            // Swap the entry being removed with the last entry.
 1488            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 1489            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 490
 491            // Clear the dense  index, for debugging purposes
 1492            DenseArray[newLength] = -1;
 493
 494            // Add the sparse index to the free list.
 1495            SparseArray[sparseIndexToRemove] = FreeIndex;
 1496            FreeIndex = sparseIndexToRemove;
 497
 1498            Count = newLength;
 1499        }
 500
 501        /// <summary>
 502        ///     Removes the associated sparse/dense index pair from active use.
 503        ///     Out parameters used to manage parallel data arrays.
 504        /// </summary>
 505        /// <param name="sparseIndexToRemove">The sparse index to remove.</param>
 506        /// <param name="indexToSwapTo">Replace the data array value at this index with the data array value at indexToS
 507        /// <param name="indexToSwapFrom">
 508        ///     Set the data array value at this index to default after swapping with the data array
 509        ///     value at indexToSwapTo.
 510        /// </param>
 511        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 512        public void RemoveUnchecked(int sparseIndexToRemove, out int indexToSwapFrom, out int indexToSwapTo)
 1513        {
 1514            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 1515            int newLength = Count - 1;
 1516            int sparseIndexBeingSwapped = DenseArray[newLength];
 517
 518            // Swap the entry being removed with the last entry.
 1519            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 1520            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 521
 522            // Clear the dense  index, for debugging purposes
 1523            DenseArray[newLength] = -1;
 524
 525            // Add the sparse index to the free list.
 1526            SparseArray[sparseIndexToRemove] = FreeIndex;
 1527            FreeIndex = sparseIndexToRemove;
 528
 1529            Count = newLength;
 530
 1531            indexToSwapTo = denseIndexToRemove;
 1532            indexToSwapFrom = newLength;
 1533        }
 534
 535        /// <summary>
 536        ///     Removes the associated sparse/dense index pair from active use and increments the version.
 537        ///     Out parameters used to manage parallel data arrays.
 538        /// </summary>
 539        /// <param name="sparseIndexToRemove">The sparse index to remove.</param>
 540        /// <param name="versionArray">The array where version numbers to check against are stored.</param>
 541        /// <param name="indexToSwapTo">Replace the data array value at this index with the data array value at indexToS
 542        /// <param name="indexToSwapFrom">
 543        ///     Set the data array value at this index to default after swapping with the data array
 544        ///     value at indexToSwapTo.
 545        /// </param>
 546        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 547        public void RemoveUnchecked(int sparseIndexToRemove, ulong[] versionArray, out int indexToSwapFrom, out int inde
 2548        {
 2549            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 2550            int newLength = Count - 1;
 2551            int sparseIndexBeingSwapped = DenseArray[newLength];
 552
 553            // Swap the entry being removed with the last entry.
 2554            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 2555            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 556
 557            // Clear the dense  index, for debugging purposes
 2558            DenseArray[newLength] = -1;
 559
 560            // Add the sparse index to the free list.
 2561            SparseArray[sparseIndexToRemove] = FreeIndex;
 2562            versionArray[sparseIndexToRemove] = versionArray[sparseIndexToRemove] + 1;
 2563            FreeIndex = sparseIndexToRemove;
 564
 2565            Count = newLength;
 566
 2567            indexToSwapTo = denseIndexToRemove;
 2568            indexToSwapFrom = newLength;
 2569        }
 570
 571        /// <summary>
 572        ///     Removes the associated sparse/dense index pair from active use.
 573        /// </summary>
 574        /// <param name="denseIndexToRemove">The dense index associated with the sparse index to remove.</param>
 575        public void RemoveUncheckedFromDenseIndex(int denseIndexToRemove)
 1576        {
 1577            int sparseIndexToRemove = DenseArray[denseIndexToRemove];
 1578            int newLength = Count - 1;
 1579            int sparseIndexBeingSwapped = DenseArray[newLength];
 580
 581            // Swap the entry being removed with the last entry.
 1582            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 1583            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 584
 585            // Clear the dense  index, for debugging purposes
 1586            DenseArray[newLength] = -1;
 587
 588            // Add the sparse index to the free list.
 1589            SparseArray[sparseIndexToRemove] = FreeIndex;
 1590            FreeIndex = sparseIndexToRemove;
 591
 1592            Count = newLength;
 1593        }
 594
 595        /// <summary>
 596        ///     Removes the associated sparse/dense index pair from active use.
 597        /// </summary>
 598        /// <param name="denseIndexToRemove">The dense index associated with the sparse index to remove.</param>
 599        /// <param name="versionArray">The array where version numbers to check against are stored.</param>
 600        public void RemoveUncheckedFromDenseIndex(int denseIndexToRemove, ulong[] versionArray)
 1601        {
 1602            int sparseIndexToRemove = DenseArray[denseIndexToRemove];
 1603            int newLength = Count - 1;
 1604            int sparseIndexBeingSwapped = DenseArray[newLength];
 605
 606            // Swap the entry being removed with the last entry.
 1607            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 1608            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 609
 610            // Clear the dense  index, for debugging purposes
 1611            DenseArray[newLength] = -1;
 612
 613            // Add the sparse index to the free list.
 1614            SparseArray[sparseIndexToRemove] = FreeIndex;
 1615            versionArray[sparseIndexToRemove] += 1;
 1616            FreeIndex = sparseIndexToRemove;
 617
 1618            Count = newLength;
 1619        }
 620
 621        /// <summary>
 622        ///     Removes the associated sparse/dense index pair from active use.
 623        ///     Out parameter used to manage parallel data arrays.
 624        /// </summary>
 625        /// <param name="denseIndexToRemove">The sparse index to remove.</param>
 626        /// <param name="indexToSwapFrom">
 627        ///     Set the data array value at this index to default after swapping with the data array
 628        ///     value at denseIndexToRemove.
 629        /// </param>
 630        public void RemoveUncheckedFromDenseIndex(int denseIndexToRemove, out int indexToSwapFrom)
 1631        {
 1632            int sparseIndexToRemove = DenseArray[denseIndexToRemove];
 1633            int newLength = Count - 1;
 1634            int sparseIndexBeingSwapped = DenseArray[newLength];
 635
 636            // Swap the entry being removed with the last entry.
 1637            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 1638            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 639
 640            // Clear the dense  index, for debugging purposes
 1641            DenseArray[newLength] = -1;
 642
 643            // Add the sparse index to the free list.
 1644            SparseArray[sparseIndexToRemove] = FreeIndex;
 1645            FreeIndex = sparseIndexToRemove;
 646
 1647            Count = newLength;
 648
 1649            indexToSwapFrom = newLength;
 1650        }
 651
 652        /// <summary>
 653        ///     Removes the associated sparse/dense index pair from active use.
 654        ///     Out parameter used to manage parallel data arrays.
 655        /// </summary>
 656        /// <param name="denseIndexToRemove">The sparse index to remove.</param>
 657        /// <param name="versionArray">The array where version numbers to check against are stored.</param>
 658        /// <param name="indexToSwapFrom">
 659        ///     Set the data array value at this index to default after swapping with the data array
 660        ///     value at denseIndexToRemove.
 661        /// </param>
 662        public void RemoveUncheckedFromDenseIndex(int denseIndexToRemove, ulong[] versionArray, out int indexToSwapFrom)
 1663        {
 1664            int sparseIndexToRemove = DenseArray[denseIndexToRemove];
 1665            int newLength = Count - 1;
 1666            int sparseIndexBeingSwapped = DenseArray[newLength];
 667
 668            // Swap the entry being removed with the last entry.
 1669            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 1670            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 671
 672            // Clear the dense  index, for debugging purposes
 1673            DenseArray[newLength] = -1;
 674
 675            // Add the sparse index to the free list.
 1676            SparseArray[sparseIndexToRemove] = FreeIndex;
 1677            versionArray[sparseIndexToRemove] = versionArray[sparseIndexToRemove] + 1;
 1678            FreeIndex = sparseIndexToRemove;
 679
 1680            Count = newLength;
 681
 1682            indexToSwapFrom = newLength;
 1683        }
 684
 685        /// <summary>
 686        ///     Clear the dense and sparse arrays.
 687        /// </summary>
 688        public void Clear()
 1689        {
 1690            int capacity = SparseArray.Length;
 8691            for (int i = 0; i < capacity; i++)
 3692            {
 3693                DenseArray[i] = -1;
 3694                SparseArray[i] = i + 1;
 3695            }
 696
 1697            FreeIndex = 0;
 1698            Count = 0;
 1699        }
 700
 701        /// <summary>
 702        ///     Clear the dense and sparse arrays.
 703        /// </summary>
 704        /// ///
 705        /// <param name="versionArray">Array containing version numbers to check against.</param>
 706        public void Clear(ulong[] versionArray)
 1707        {
 1708            int capacity = SparseArray.Length;
 8709            for (int i = 0; i < capacity; i++)
 3710            {
 3711                DenseArray[i] = -1;
 3712                SparseArray[i] = i + 1;
 3713                versionArray[i] = versionArray[i] + 1;
 3714            }
 715
 1716            FreeIndex = 0;
 1717            Count = 0;
 1718        }
 719
 720        /// <summary>
 721        ///     Clear the dense and sparse arrays and reset the version array.
 722        ///     Note: Only clear the version array if you are sure there are no outstanding dependencies on version numb
 723        /// </summary>
 724        /// ///
 725        /// <param name="versionArray">Array containing version numbers to check against.</param>
 726        public void ClearWithVersionArrayReset(ulong[] versionArray)
 1727        {
 1728            int capacity = SparseArray.Length;
 8729            for (int i = 0; i < capacity; i++)
 3730            {
 3731                DenseArray[i] = -1;
 3732                SparseArray[i] = i + 1;
 3733                versionArray[i] = 1;
 3734            }
 735
 1736            FreeIndex = 0;
 1737            Count = 0;
 1738        }
 739
 740        /// <summary>
 741        ///     Reallocate the dense and sparse arrays with additional capacity.
 742        /// </summary>
 743        /// <param name="extraCapacity">How many indices to expand the dense and sparse arrays by.</param>
 744        public void Expand(int extraCapacity)
 1745        {
 1746            int currentCapacity = SparseArray.Length;
 1747            int newCapacity = currentCapacity + extraCapacity;
 748
 1749            int[] newSparseArray = new int[newCapacity];
 1750            Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 1751            SparseArray = newSparseArray;
 752
 1753            int[] newDenseArray = new int[newCapacity];
 1754            Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 1755            DenseArray = newDenseArray;
 756
 8757            for (int i = currentCapacity; i < newCapacity; i++)
 3758            {
 3759                DenseArray[i] = -1; // Set new dense indices as unclaimed.
 3760                SparseArray[i] = i + 1; // Build the free list chain.
 3761            }
 1762        }
 763
 764        /// <summary>
 765        ///     Reallocate the dense and sparse arrays with additional capacity.
 766        /// </summary>
 767        /// <param name="extraCapacity">How many indices to expand the dense and sparse arrays by.</param>
 768        /// <param name="versionArray">Array containing version numbers to check against.</param>
 769        public void Expand(int extraCapacity, ref ulong[] versionArray)
 2770        {
 2771            int currentCapacity = SparseArray.Length;
 2772            int newCapacity = currentCapacity + extraCapacity;
 773
 2774            int[] newSparseArray = new int[newCapacity];
 2775            Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 2776            SparseArray = newSparseArray;
 777
 2778            int[] newDenseArray = new int[newCapacity];
 2779            Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 2780            DenseArray = newDenseArray;
 781
 2782            ulong[] newVersionArray = new ulong[newCapacity];
 2783            Array.Copy(versionArray, 0, newVersionArray, 0, currentCapacity);
 2784            versionArray = newVersionArray;
 785
 16786            for (int i = currentCapacity; i < newCapacity; i++)
 6787            {
 6788                DenseArray[i] = -1; // Set new dense indices as unclaimed.
 6789                SparseArray[i] = i + 1; // Build the free list chain.
 6790                versionArray[i] = 1;
 6791            }
 2792        }
 793
 794        public void Reserve(int numberToReserve)
 1795        {
 1796            int currentCapacity = SparseArray.Length;
 1797            int currentCount = Count;
 1798            int newCount = currentCount + numberToReserve;
 799
 1800            if (newCount > currentCapacity)
 1801            {
 1802                int[] newSparseArray = new int[newCount];
 1803                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 1804                SparseArray = newSparseArray;
 805
 1806                int[] newDenseArray = new int[newCount];
 1807                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 1808                DenseArray = newDenseArray;
 809
 4810                for (int i = currentCapacity; i < newCount; i++)
 1811                {
 1812                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 1813                    SparseArray[i] = i + 1; // Build the free list chain.
 1814                }
 1815            }
 1816        }
 817
 818        public void Reserve(int numberToReserve, ref ulong[] versionArray)
 0819        {
 0820            int currentCapacity = SparseArray.Length;
 0821            int currentCount = Count;
 0822            int newCount = currentCount + numberToReserve;
 823
 0824            if (newCount > currentCapacity)
 0825            {
 0826                int[] newSparseArray = new int[newCount];
 0827                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 0828                SparseArray = newSparseArray;
 829
 0830                int[] newDenseArray = new int[newCount];
 0831                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 0832                DenseArray = newDenseArray;
 833
 0834                ulong[] newVersionArray = new ulong[newCount];
 0835                Array.Copy(versionArray, 0, newVersionArray, 0, currentCapacity);
 0836                versionArray = newVersionArray;
 837
 0838                for (int i = currentCapacity; i < newCount; i++)
 0839                {
 0840                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 0841                    SparseArray[i] = i + 1; // Build the free list chain.
 0842                    versionArray[i] = 1;
 0843                }
 0844            }
 0845        }
 846
 847        #region Parallel array method duplicates
 848
 849        /// <summary>
 850        ///     Adds a sparse/dense index pair to the set and expands the arrays if necessary.
 851        /// </summary>
 852        /// <returns>True if the index pool expanded.</returns>
 853        public bool AddWithExpandCheck<T0>(T0 obj0, ref T0[] array0, out int lookupIndex, int howMuchToExpand = 16)
 0854        {
 0855            int indexToClaim = FreeIndex;
 0856            int currentCapacity = SparseArray.Length;
 0857            bool needsExpansion = false;
 858
 0859            if (indexToClaim >= currentCapacity)
 0860            {
 0861                needsExpansion = true;
 862                // We're out of space, the last free index points to nothing. Allocate more indices.
 0863                int newCapacity = currentCapacity + howMuchToExpand;
 864
 0865                int[] newSparseArray = new int[newCapacity];
 0866                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 0867                SparseArray = newSparseArray;
 868
 0869                int[] newDenseArray = new int[newCapacity];
 0870                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 0871                DenseArray = newDenseArray;
 872
 0873                T0[] newArray0 = new T0[newCapacity];
 0874                Array.Copy(array0, 0, newArray0, 0, currentCapacity);
 0875                array0 = newArray0;
 876
 0877                for (int i = currentCapacity; i < newCapacity; i++)
 0878                {
 0879                    SparseArray[i] = i + 1; // Build the free list chain.
 0880                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 0881                }
 0882            }
 883
 0884            int nextFreeIndex = SparseArray[indexToClaim];
 885
 0886            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 0887            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 888
 0889            array0[Count] = obj0;
 890
 0891            ++Count;
 0892            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 893
 0894            lookupIndex = indexToClaim;
 0895            return needsExpansion;
 0896        }
 897
 898        /// <summary>
 899        ///     Adds a sparse/dense index pair to the set and expands the arrays if necessary.
 900        /// </summary>
 901        /// <returns>True if the index pool expanded.</returns>
 902        public bool AddWithExpandCheck<T0, T1>(T0 obj0, ref T0[] array0, T1 obj1, ref T1[] array1, out int lookupIndex,
 903            int howMuchToExpand = 16)
 0904        {
 0905            int indexToClaim = FreeIndex;
 0906            int currentCapacity = SparseArray.Length;
 0907            bool needsExpansion = false;
 908
 0909            if (indexToClaim >= currentCapacity)
 0910            {
 0911                needsExpansion = true;
 912                // We're out of space, the last free index points to nothing. Allocate more indices.
 0913                int newCapacity = currentCapacity + howMuchToExpand;
 914
 0915                int[] newSparseArray = new int[newCapacity];
 0916                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 0917                SparseArray = newSparseArray;
 918
 0919                int[] newDenseArray = new int[newCapacity];
 0920                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 0921                DenseArray = newDenseArray;
 922
 0923                T0[] newArray0 = new T0[newCapacity];
 0924                Array.Copy(array0, 0, newArray0, 0, currentCapacity);
 0925                array0 = newArray0;
 926
 0927                T1[] newArray1 = new T1[newCapacity];
 0928                Array.Copy(array1, 0, newArray1, 0, currentCapacity);
 0929                array1 = newArray1;
 930
 0931                for (int i = currentCapacity; i < newCapacity; i++)
 0932                {
 0933                    SparseArray[i] = i + 1; // Build the free list chain.
 0934                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 0935                }
 0936            }
 937
 0938            int nextFreeIndex = SparseArray[indexToClaim];
 939
 0940            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 0941            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 942
 0943            array0[Count] = obj0;
 0944            array1[Count] = obj1;
 945
 0946            ++Count;
 0947            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 948
 0949            lookupIndex = indexToClaim;
 0950            return needsExpansion;
 0951        }
 952
 953        /// <summary>
 954        ///     Adds a sparse/dense index pair to the set and expands the arrays if necessary.
 955        /// </summary>
 956        /// <returns>True if the index pool expanded.</returns>
 957        public bool AddWithExpandCheck<T0, T1, T2>(T0 obj0, ref T0[] array0, T1 obj1, ref T1[] array1, T2 obj2,
 958            ref T2[] array2,
 959            out int lookupIndex, int howMuchToExpand = 16)
 0960        {
 0961            int indexToClaim = FreeIndex;
 0962            int currentCapacity = SparseArray.Length;
 0963            bool needsExpansion = false;
 964
 0965            if (indexToClaim >= currentCapacity)
 0966            {
 0967                needsExpansion = true;
 968                // We're out of space, the last free index points to nothing. Allocate more indices.
 0969                int newCapacity = currentCapacity + howMuchToExpand;
 970
 0971                int[] newSparseArray = new int[newCapacity];
 0972                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 0973                SparseArray = newSparseArray;
 974
 0975                int[] newDenseArray = new int[newCapacity];
 0976                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 0977                DenseArray = newDenseArray;
 978
 0979                T0[] newArray0 = new T0[newCapacity];
 0980                Array.Copy(array0, 0, newArray0, 0, currentCapacity);
 0981                array0 = newArray0;
 982
 0983                T1[] newArray1 = new T1[newCapacity];
 0984                Array.Copy(array1, 0, newArray1, 0, currentCapacity);
 0985                array1 = newArray1;
 986
 0987                T2[] newArray2 = new T2[newCapacity];
 0988                Array.Copy(array2, 0, newArray2, 0, currentCapacity);
 0989                array2 = newArray2;
 990
 0991                for (int i = currentCapacity; i < newCapacity; i++)
 0992                {
 0993                    SparseArray[i] = i + 1; // Build the free list chain.
 0994                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 0995                }
 0996            }
 997
 0998            int nextFreeIndex = SparseArray[indexToClaim];
 999
 01000            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01001            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1002
 01003            array0[Count] = obj0;
 01004            array1[Count] = obj1;
 01005            array2[Count] = obj2;
 1006
 01007            ++Count;
 01008            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1009
 01010            lookupIndex = indexToClaim;
 01011            return needsExpansion;
 01012        }
 1013
 1014        /// <summary>
 1015        ///     Adds a sparse/dense index pair to the set and expands the arrays if necessary.
 1016        /// </summary>
 1017        /// <returns>True if the index pool expanded.</returns>
 1018        public bool AddWithExpandCheck<T0, T1, T2, T3>(T0 obj0, ref T0[] array0, T1 obj1, ref T1[] array1, T2 obj2,
 1019            ref T2[] array2, T3 obj3, ref T3[] array3, out int lookupIndex, int howMuchToExpand = 16)
 01020        {
 01021            int indexToClaim = FreeIndex;
 01022            int currentCapacity = SparseArray.Length;
 01023            bool needsExpansion = false;
 1024
 01025            if (indexToClaim >= currentCapacity)
 01026            {
 01027                needsExpansion = true;
 1028                // We're out of space, the last free index points to nothing. Allocate more indices.
 01029                int newCapacity = currentCapacity + howMuchToExpand;
 1030
 01031                int[] newSparseArray = new int[newCapacity];
 01032                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 01033                SparseArray = newSparseArray;
 1034
 01035                int[] newDenseArray = new int[newCapacity];
 01036                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 01037                DenseArray = newDenseArray;
 1038
 01039                T0[] newArray0 = new T0[newCapacity];
 01040                Array.Copy(array0, 0, newArray0, 0, currentCapacity);
 01041                array0 = newArray0;
 1042
 01043                T1[] newArray1 = new T1[newCapacity];
 01044                Array.Copy(array1, 0, newArray1, 0, currentCapacity);
 01045                array1 = newArray1;
 1046
 01047                T2[] newArray2 = new T2[newCapacity];
 01048                Array.Copy(array2, 0, newArray2, 0, currentCapacity);
 01049                array2 = newArray2;
 1050
 01051                T3[] newArray3 = new T3[newCapacity];
 01052                Array.Copy(array3, 0, newArray3, 0, currentCapacity);
 01053                array3 = newArray3;
 1054
 01055                for (int i = currentCapacity; i < newCapacity; i++)
 01056                {
 01057                    SparseArray[i] = i + 1; // Build the free list chain.
 01058                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 01059                }
 01060            }
 1061
 01062            int nextFreeIndex = SparseArray[indexToClaim];
 1063
 01064            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01065            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1066
 01067            array0[Count] = obj0;
 01068            array1[Count] = obj1;
 01069            array2[Count] = obj2;
 01070            array3[Count] = obj3;
 1071
 01072            ++Count;
 01073            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1074
 01075            lookupIndex = indexToClaim;
 01076            return needsExpansion;
 01077        }
 1078
 1079        /// <summary>
 1080        ///     Adds a sparse/dense index pair to the set and expands the arrays if necessary.
 1081        /// </summary>
 1082        /// <returns>True if the index pool expanded.</returns>
 1083        public bool AddWithExpandCheck<T0, T1, T2, T3, T4>(T0 obj0, ref T0[] array0, T1 obj1, ref T1[] array1, T2 obj2,
 1084            ref T2[] array2, T3 obj3, ref T3[] array3, T4 obj4, ref T4[] array4, out int lookupIndex,
 1085            int howMuchToExpand = 16)
 01086        {
 01087            int indexToClaim = FreeIndex;
 01088            int currentCapacity = SparseArray.Length;
 01089            bool needsExpansion = false;
 1090
 01091            if (indexToClaim >= currentCapacity)
 01092            {
 01093                needsExpansion = true;
 1094                // We're out of space, the last free index points to nothing. Allocate more indices.
 01095                int newCapacity = currentCapacity + howMuchToExpand;
 1096
 01097                int[] newSparseArray = new int[newCapacity];
 01098                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 01099                SparseArray = newSparseArray;
 1100
 01101                int[] newDenseArray = new int[newCapacity];
 01102                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 01103                DenseArray = newDenseArray;
 1104
 01105                T0[] newArray0 = new T0[newCapacity];
 01106                Array.Copy(array0, 0, newArray0, 0, currentCapacity);
 01107                array0 = newArray0;
 1108
 01109                T1[] newArray1 = new T1[newCapacity];
 01110                Array.Copy(array1, 0, newArray1, 0, currentCapacity);
 01111                array1 = newArray1;
 1112
 01113                T2[] newArray2 = new T2[newCapacity];
 01114                Array.Copy(array2, 0, newArray2, 0, currentCapacity);
 01115                array2 = newArray2;
 1116
 01117                T3[] newArray3 = new T3[newCapacity];
 01118                Array.Copy(array3, 0, newArray3, 0, currentCapacity);
 01119                array3 = newArray3;
 1120
 01121                T4[] newArray4 = new T4[newCapacity];
 01122                Array.Copy(array4, 0, newArray4, 0, currentCapacity);
 01123                array4 = newArray4;
 1124
 01125                for (int i = currentCapacity; i < newCapacity; i++)
 01126                {
 01127                    SparseArray[i] = i + 1; // Build the free list chain.
 01128                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 01129                }
 01130            }
 1131
 01132            int nextFreeIndex = SparseArray[indexToClaim];
 1133
 01134            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01135            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1136
 01137            array0[Count] = obj0;
 01138            array1[Count] = obj1;
 01139            array2[Count] = obj2;
 01140            array3[Count] = obj3;
 01141            array4[Count] = obj4;
 1142
 01143            ++Count;
 01144            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1145
 01146            lookupIndex = indexToClaim;
 01147            return needsExpansion;
 01148        }
 1149
 1150        /// <summary>
 1151        ///     Adds a sparse/dense index pair to the set and expands the arrays if necessary.
 1152        /// </summary>
 1153        /// <returns>True if the index pool expanded.</returns>
 1154        public bool AddWithExpandCheck<T0, T1, T2, T3, T4, T5>(T0 obj0, ref T0[] array0, T1 obj1, ref T1[] array1,
 1155            T2 obj2,
 1156            ref T2[] array2, T3 obj3, ref T3[] array3, T4 obj4, ref T4[] array4, T5 obj5, ref T5[] array5,
 1157            out int lookupIndex, int howMuchToExpand = 16)
 01158        {
 01159            int indexToClaim = FreeIndex;
 01160            int currentCapacity = SparseArray.Length;
 01161            bool needsExpansion = false;
 1162
 01163            if (indexToClaim >= currentCapacity)
 01164            {
 01165                needsExpansion = true;
 1166                // We're out of space, the last free index points to nothing. Allocate more indices.
 01167                int newCapacity = currentCapacity + howMuchToExpand;
 1168
 01169                int[] newSparseArray = new int[newCapacity];
 01170                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 01171                SparseArray = newSparseArray;
 1172
 01173                int[] newDenseArray = new int[newCapacity];
 01174                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 01175                DenseArray = newDenseArray;
 1176
 01177                T0[] newArray0 = new T0[newCapacity];
 01178                Array.Copy(array0, 0, newArray0, 0, currentCapacity);
 01179                array0 = newArray0;
 1180
 01181                T1[] newArray1 = new T1[newCapacity];
 01182                Array.Copy(array1, 0, newArray1, 0, currentCapacity);
 01183                array1 = newArray1;
 1184
 01185                T2[] newArray2 = new T2[newCapacity];
 01186                Array.Copy(array2, 0, newArray2, 0, currentCapacity);
 01187                array2 = newArray2;
 1188
 01189                T3[] newArray3 = new T3[newCapacity];
 01190                Array.Copy(array3, 0, newArray3, 0, currentCapacity);
 01191                array3 = newArray3;
 1192
 01193                T4[] newArray4 = new T4[newCapacity];
 01194                Array.Copy(array4, 0, newArray4, 0, currentCapacity);
 01195                array4 = newArray4;
 1196
 01197                T5[] newArray5 = new T5[newCapacity];
 01198                Array.Copy(array5, 0, newArray5, 0, currentCapacity);
 01199                array5 = newArray5;
 1200
 01201                for (int i = currentCapacity; i < newCapacity; i++)
 01202                {
 01203                    SparseArray[i] = i + 1; // Build the free list chain.
 01204                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 01205                }
 01206            }
 1207
 01208            int nextFreeIndex = SparseArray[indexToClaim];
 1209
 01210            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01211            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1212
 01213            array0[Count] = obj0;
 01214            array1[Count] = obj1;
 01215            array2[Count] = obj2;
 01216            array3[Count] = obj3;
 01217            array4[Count] = obj4;
 01218            array5[Count] = obj5;
 1219
 01220            ++Count;
 01221            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1222
 01223            lookupIndex = indexToClaim;
 01224            return needsExpansion;
 01225        }
 1226
 1227        /// <summary>
 1228        ///     Adds a sparse/dense index pair to the set and expands the arrays if necessary.
 1229        /// </summary>
 1230        /// <returns>True if the index pool expanded.</returns>
 1231        public bool AddWithExpandCheck<T0, T1, T2, T3, T4, T5, T6>(T0 obj0, ref T0[] array0, T1 obj1, ref T1[] array1,
 1232            T2 obj2,
 1233            ref T2[] array2, T3 obj3, ref T3[] array3, T4 obj4, ref T4[] array4, T5 obj5, ref T5[] array5, T6 obj6,
 1234            ref T6[] array6, out int lookupIndex, int howMuchToExpand = 16)
 01235        {
 01236            int indexToClaim = FreeIndex;
 01237            int currentCapacity = SparseArray.Length;
 01238            bool needsExpansion = false;
 1239
 01240            if (indexToClaim >= currentCapacity)
 01241            {
 01242                needsExpansion = true;
 1243                // We're out of space, the last free index points to nothing. Allocate more indices.
 01244                int newCapacity = currentCapacity + howMuchToExpand;
 1245
 01246                int[] newSparseArray = new int[newCapacity];
 01247                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 01248                SparseArray = newSparseArray;
 1249
 01250                int[] newDenseArray = new int[newCapacity];
 01251                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 01252                DenseArray = newDenseArray;
 1253
 01254                T0[] newArray0 = new T0[newCapacity];
 01255                Array.Copy(array0, 0, newArray0, 0, currentCapacity);
 01256                array0 = newArray0;
 1257
 01258                T1[] newArray1 = new T1[newCapacity];
 01259                Array.Copy(array1, 0, newArray1, 0, currentCapacity);
 01260                array1 = newArray1;
 1261
 01262                T2[] newArray2 = new T2[newCapacity];
 01263                Array.Copy(array2, 0, newArray2, 0, currentCapacity);
 01264                array2 = newArray2;
 1265
 01266                T3[] newArray3 = new T3[newCapacity];
 01267                Array.Copy(array3, 0, newArray3, 0, currentCapacity);
 01268                array3 = newArray3;
 1269
 01270                T4[] newArray4 = new T4[newCapacity];
 01271                Array.Copy(array4, 0, newArray4, 0, currentCapacity);
 01272                array4 = newArray4;
 1273
 01274                T5[] newArray5 = new T5[newCapacity];
 01275                Array.Copy(array5, 0, newArray5, 0, currentCapacity);
 01276                array5 = newArray5;
 1277
 01278                T6[] newArray6 = new T6[newCapacity];
 01279                Array.Copy(array6, 0, newArray6, 0, currentCapacity);
 01280                array6 = newArray6;
 1281
 01282                for (int i = currentCapacity; i < newCapacity; i++)
 01283                {
 01284                    SparseArray[i] = i + 1; // Build the free list chain.
 01285                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 01286                }
 01287            }
 1288
 01289            int nextFreeIndex = SparseArray[indexToClaim];
 1290
 01291            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01292            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1293
 01294            array0[Count] = obj0;
 01295            array1[Count] = obj1;
 01296            array2[Count] = obj2;
 01297            array3[Count] = obj3;
 01298            array4[Count] = obj4;
 01299            array5[Count] = obj5;
 01300            array6[Count] = obj6;
 1301
 01302            ++Count;
 01303            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1304
 01305            lookupIndex = indexToClaim;
 01306            return needsExpansion;
 01307        }
 1308
 1309        /// <summary>
 1310        ///     Adds a sparse/dense index pair to the set and expands the arrays if necessary.
 1311        /// </summary>
 1312        /// <returns>True if the index pool expanded.</returns>
 1313        public bool AddWithExpandCheck<T0, T1, T2, T3, T4, T5, T6, T7>(T0 obj0, ref T0[] array0, T1 obj1,
 1314            ref T1[] array1, T2 obj2,
 1315            ref T2[] array2, T3 obj3, ref T3[] array3, T4 obj4, ref T4[] array4, T5 obj5, ref T5[] array5, T6 obj6,
 1316            ref T6[] array6, T7 obj7, ref T7[] array7, out int lookupIndex, int howMuchToExpand = 16)
 01317        {
 01318            int indexToClaim = FreeIndex;
 01319            int currentCapacity = SparseArray.Length;
 01320            bool needsExpansion = false;
 1321
 01322            if (indexToClaim >= currentCapacity)
 01323            {
 01324                needsExpansion = true;
 1325                // We're out of space, the last free index points to nothing. Allocate more indices.
 01326                int newCapacity = currentCapacity + howMuchToExpand;
 1327
 01328                int[] newSparseArray = new int[newCapacity];
 01329                Array.Copy(SparseArray, 0, newSparseArray, 0, currentCapacity);
 01330                SparseArray = newSparseArray;
 1331
 01332                int[] newDenseArray = new int[newCapacity];
 01333                Array.Copy(DenseArray, 0, newDenseArray, 0, currentCapacity);
 01334                DenseArray = newDenseArray;
 1335
 01336                T0[] newArray0 = new T0[newCapacity];
 01337                Array.Copy(array0, 0, newArray0, 0, currentCapacity);
 01338                array0 = newArray0;
 1339
 01340                T1[] newArray1 = new T1[newCapacity];
 01341                Array.Copy(array1, 0, newArray1, 0, currentCapacity);
 01342                array1 = newArray1;
 1343
 01344                T2[] newArray2 = new T2[newCapacity];
 01345                Array.Copy(array2, 0, newArray2, 0, currentCapacity);
 01346                array2 = newArray2;
 1347
 01348                T3[] newArray3 = new T3[newCapacity];
 01349                Array.Copy(array3, 0, newArray3, 0, currentCapacity);
 01350                array3 = newArray3;
 1351
 01352                T4[] newArray4 = new T4[newCapacity];
 01353                Array.Copy(array4, 0, newArray4, 0, currentCapacity);
 01354                array4 = newArray4;
 1355
 01356                T5[] newArray5 = new T5[newCapacity];
 01357                Array.Copy(array5, 0, newArray5, 0, currentCapacity);
 01358                array5 = newArray5;
 1359
 01360                T6[] newArray6 = new T6[newCapacity];
 01361                Array.Copy(array6, 0, newArray6, 0, currentCapacity);
 01362                array6 = newArray6;
 1363
 01364                T7[] newArray7 = new T7[newCapacity];
 01365                Array.Copy(array7, 0, newArray7, 0, currentCapacity);
 01366                array7 = newArray7;
 1367
 01368                for (int i = currentCapacity; i < newCapacity; i++)
 01369                {
 01370                    SparseArray[i] = i + 1; // Build the free list chain.
 01371                    DenseArray[i] = -1; // Set new dense indices as unclaimed.
 01372                }
 01373            }
 1374
 01375            int nextFreeIndex = SparseArray[indexToClaim];
 1376
 01377            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01378            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1379
 01380            array0[Count] = obj0;
 01381            array1[Count] = obj1;
 01382            array2[Count] = obj2;
 01383            array3[Count] = obj3;
 01384            array4[Count] = obj4;
 01385            array5[Count] = obj5;
 01386            array6[Count] = obj6;
 01387            array7[Count] = obj7;
 1388
 01389            ++Count;
 01390            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1391
 01392            lookupIndex = indexToClaim;
 01393            return needsExpansion;
 01394        }
 1395
 1396        /// <summary>
 1397        ///     Adds to the set without checking if the set needs to expand.
 1398        /// </summary>
 1399        /// <returns>The sparse index allocated</returns>
 1400        public int AddUnchecked<T0>(T0 obj0, T0[] array0)
 01401        {
 01402            int indexToClaim = FreeIndex;
 01403            int nextFreeIndex = SparseArray[indexToClaim];
 01404            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01405            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1406
 01407            array0[Count] = obj0;
 1408
 01409            ++Count;
 01410            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1411
 01412            return indexToClaim;
 01413        }
 1414
 1415        /// <summary>
 1416        ///     Adds to the set without checking if the set needs to expand.
 1417        /// </summary>
 1418        /// <returns>The sparse index allocated</returns>
 1419        public int AddUnchecked<T0, T1>(T0 obj0, T0[] array0, T1 obj1, T1[] array1)
 01420        {
 01421            int indexToClaim = FreeIndex;
 01422            int nextFreeIndex = SparseArray[indexToClaim];
 01423            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01424            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1425
 01426            array0[Count] = obj0;
 01427            array1[Count] = obj1;
 1428
 01429            ++Count;
 01430            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1431
 01432            return indexToClaim;
 01433        }
 1434
 1435        /// <summary>
 1436        ///     Adds to the set without checking if the set needs to expand.
 1437        /// </summary>
 1438        /// <returns>The sparse index allocated</returns>
 1439        public int AddUnchecked<T0, T1, T2>(T0 obj0, T0[] array0, T1 obj1, T1[] array1, T2 obj2, T2[] array2)
 01440        {
 01441            int indexToClaim = FreeIndex;
 01442            int nextFreeIndex = SparseArray[indexToClaim];
 01443            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01444            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1445
 01446            array0[Count] = obj0;
 01447            array1[Count] = obj1;
 01448            array2[Count] = obj2;
 1449
 01450            ++Count;
 01451            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1452
 01453            return indexToClaim;
 01454        }
 1455
 1456        /// <summary>
 1457        ///     Adds to the set without checking if the set needs to expand.
 1458        /// </summary>
 1459        /// <returns>The sparse index allocated</returns>
 1460        public int AddUnchecked<T0, T1, T2, T3>(T0 obj0, T0[] array0, T1 obj1, T1[] array1, T2 obj2, T2[] array2,
 1461            T3 obj3,
 1462            T3[] array3)
 01463        {
 01464            int indexToClaim = FreeIndex;
 01465            int nextFreeIndex = SparseArray[indexToClaim];
 01466            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01467            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1468
 01469            array0[Count] = obj0;
 01470            array1[Count] = obj1;
 01471            array2[Count] = obj2;
 01472            array3[Count] = obj3;
 1473
 01474            ++Count;
 01475            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1476
 01477            return indexToClaim;
 01478        }
 1479
 1480        /// <summary>
 1481        ///     Adds to the set without checking if the set needs to expand.
 1482        /// </summary>
 1483        /// <returns>The sparse index allocated</returns>
 1484        public int AddUnchecked<T0, T1, T2, T3, T4>(T0 obj0, T0[] array0, T1 obj1, T1[] array1, T2 obj2, T2[] array2,
 1485            T3 obj3, T3[] array3, T4 obj4, T4[] array4)
 01486        {
 01487            int indexToClaim = FreeIndex;
 01488            int nextFreeIndex = SparseArray[indexToClaim];
 01489            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01490            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1491
 01492            array0[Count] = obj0;
 01493            array1[Count] = obj1;
 01494            array2[Count] = obj2;
 01495            array3[Count] = obj3;
 01496            array4[Count] = obj4;
 1497
 01498            ++Count;
 01499            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1500
 01501            return indexToClaim;
 01502        }
 1503
 1504        /// <summary>
 1505        ///     Adds to the set without checking if the set needs to expand.
 1506        /// </summary>
 1507        /// <returns>The sparse index allocated</returns>
 1508        public int AddUnchecked<T0, T1, T2, T3, T4, T5>(T0 obj0, T0[] array0, T1 obj1, T1[] array1, T2 obj2,
 1509            T2[] array2,
 1510            T3 obj3, T3[] array3, T4 obj4, T4[] array4, T5 obj5, T5[] array5)
 01511        {
 01512            int indexToClaim = FreeIndex;
 01513            int nextFreeIndex = SparseArray[indexToClaim];
 01514            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01515            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1516
 01517            array0[Count] = obj0;
 01518            array1[Count] = obj1;
 01519            array2[Count] = obj2;
 01520            array3[Count] = obj3;
 01521            array4[Count] = obj4;
 01522            array5[Count] = obj5;
 1523
 01524            ++Count;
 01525            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1526
 01527            return indexToClaim;
 01528        }
 1529
 1530        /// <summary>
 1531        ///     Adds to the set without checking if the set needs to expand.
 1532        /// </summary>
 1533        /// <returns>The sparse index allocated</returns>
 1534        public int AddUnchecked<T0, T1, T2, T3, T4, T5, T6>(T0 obj0, T0[] array0, T1 obj1, T1[] array1, T2 obj2,
 1535            T2[] array2,
 1536            T3 obj3, T3[] array3, T4 obj4, T4[] array4, T5 obj5, T5[] array5, T6 obj6, T6[] array6)
 01537        {
 01538            int indexToClaim = FreeIndex;
 01539            int nextFreeIndex = SparseArray[indexToClaim];
 01540            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01541            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1542
 01543            array0[Count] = obj0;
 01544            array1[Count] = obj1;
 01545            array2[Count] = obj2;
 01546            array3[Count] = obj3;
 01547            array4[Count] = obj4;
 01548            array5[Count] = obj5;
 01549            array6[Count] = obj6;
 1550
 01551            ++Count;
 01552            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1553
 01554            return indexToClaim;
 01555        }
 1556
 1557        /// <summary>
 1558        ///     Adds to the set without checking if the set needs to expand.
 1559        /// </summary>
 1560        /// <returns>The sparse index allocated</returns>
 1561        public int AddUnchecked<T0, T1, T2, T3, T4, T5, T6, T7>(T0 obj0, T0[] array0, T1 obj1, T1[] array1, T2 obj2,
 1562            T2[] array2, T3 obj3, T3[] array3, T4 obj4, T4[] array4, T5 obj5, T5[] array5, T6 obj6, T6[] array6,
 1563            T7 obj7, T7[] array7)
 01564        {
 01565            int indexToClaim = FreeIndex;
 01566            int nextFreeIndex = SparseArray[indexToClaim];
 01567            DenseArray[Count] = indexToClaim; // Point the next dense id at our newly claimed sparse index.
 01568            SparseArray[indexToClaim] = Count; // Point our newly claimed sparse index at the dense index.
 1569
 01570            array0[Count] = obj0;
 01571            array1[Count] = obj1;
 01572            array2[Count] = obj2;
 01573            array3[Count] = obj3;
 01574            array4[Count] = obj4;
 01575            array5[Count] = obj5;
 01576            array6[Count] = obj6;
 01577            array7[Count] = obj7;
 1578
 01579            ++Count;
 01580            FreeIndex = nextFreeIndex; // Set the free list head for next time.
 1581
 01582            return indexToClaim;
 01583        }
 1584
 1585        public void RemoveUnchecked<T0>(int sparseIndexToRemove, T0[] array0)
 01586        {
 01587            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 01588            int newLength = Count - 1;
 01589            int sparseIndexBeingSwapped = DenseArray[newLength];
 1590
 1591            // Swap the entry being removed with the last entry.
 01592            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 01593            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 01594            array0[denseIndexToRemove] = array0[newLength];
 1595
 1596            // Clear the dense  index, for debugging purposes
 01597            DenseArray[newLength] = -1;
 01598            array0[newLength] = default;
 1599
 1600            // Add the sparse index to the free list.
 01601            SparseArray[sparseIndexToRemove] = FreeIndex;
 01602            FreeIndex = sparseIndexToRemove;
 1603
 01604            Count = newLength;
 01605        }
 1606
 1607        public void RemoveUnchecked<T0, T1>(int sparseIndexToRemove, T0[] array0, T1[] array1)
 01608        {
 01609            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 01610            int newLength = Count - 1;
 01611            int sparseIndexBeingSwapped = DenseArray[newLength];
 1612
 1613            // Swap the entry being removed with the last entry.
 01614            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 01615            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 01616            array0[denseIndexToRemove] = array0[newLength];
 01617            array1[denseIndexToRemove] = array1[newLength];
 1618
 1619            // Clear the dense  index, for debugging purposes
 01620            DenseArray[newLength] = -1;
 01621            array0[newLength] = default;
 01622            array1[newLength] = default;
 1623
 1624            // Add the sparse index to the free list.
 01625            SparseArray[sparseIndexToRemove] = FreeIndex;
 01626            FreeIndex = sparseIndexToRemove;
 1627
 01628            Count = newLength;
 01629        }
 1630
 1631        public void RemoveUnchecked<T0, T1, T2>(int sparseIndexToRemove, T0[] array0, T1[] array1, T2[] array2)
 01632        {
 01633            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 01634            int newLength = Count - 1;
 01635            int sparseIndexBeingSwapped = DenseArray[newLength];
 1636
 1637            // Swap the entry being removed with the last entry.
 01638            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 01639            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 01640            array0[denseIndexToRemove] = array0[newLength];
 01641            array1[denseIndexToRemove] = array1[newLength];
 01642            array2[denseIndexToRemove] = array2[newLength];
 1643
 1644            // Clear the dense  index, for debugging purposes
 01645            DenseArray[newLength] = -1;
 01646            array0[newLength] = default;
 01647            array1[newLength] = default;
 01648            array2[newLength] = default;
 1649
 1650            // Add the sparse index to the free list.
 01651            SparseArray[sparseIndexToRemove] = FreeIndex;
 01652            FreeIndex = sparseIndexToRemove;
 1653
 01654            Count = newLength;
 01655        }
 1656
 1657        public void RemoveUnchecked<T0, T1, T2, T3>(int sparseIndexToRemove, T0[] array0, T1[] array1, T2[] array2,
 1658            T3[] array3)
 01659        {
 01660            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 01661            int newLength = Count - 1;
 01662            int sparseIndexBeingSwapped = DenseArray[newLength];
 1663
 1664            // Swap the entry being removed with the last entry.
 01665            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 01666            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 01667            array0[denseIndexToRemove] = array0[newLength];
 01668            array1[denseIndexToRemove] = array1[newLength];
 01669            array2[denseIndexToRemove] = array2[newLength];
 01670            array3[denseIndexToRemove] = array3[newLength];
 1671
 1672            // Clear the dense  index, for debugging purposes
 01673            DenseArray[newLength] = -1;
 01674            array0[newLength] = default;
 01675            array1[newLength] = default;
 01676            array2[newLength] = default;
 01677            array3[newLength] = default;
 1678
 1679            // Add the sparse index to the free list.
 01680            SparseArray[sparseIndexToRemove] = FreeIndex;
 01681            FreeIndex = sparseIndexToRemove;
 1682
 01683            Count = newLength;
 01684        }
 1685
 1686        public void RemoveUnchecked<T0, T1, T2, T3, T4>(int sparseIndexToRemove, T0[] array0, T1[] array1, T2[] array2,
 1687            T3[] array3, T4[] array4)
 01688        {
 01689            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 01690            int newLength = Count - 1;
 01691            int sparseIndexBeingSwapped = DenseArray[newLength];
 1692
 1693            // Swap the entry being removed with the last entry.
 01694            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 01695            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 01696            array0[denseIndexToRemove] = array0[newLength];
 01697            array1[denseIndexToRemove] = array1[newLength];
 01698            array2[denseIndexToRemove] = array2[newLength];
 01699            array3[denseIndexToRemove] = array3[newLength];
 01700            array4[denseIndexToRemove] = array4[newLength];
 1701
 1702            // Clear the dense  index, for debugging purposes
 01703            DenseArray[newLength] = -1;
 01704            array0[newLength] = default;
 01705            array1[newLength] = default;
 01706            array2[newLength] = default;
 01707            array3[newLength] = default;
 01708            array4[newLength] = default;
 1709
 1710            // Add the sparse index to the free list.
 01711            SparseArray[sparseIndexToRemove] = FreeIndex;
 01712            FreeIndex = sparseIndexToRemove;
 1713
 01714            Count = newLength;
 01715        }
 1716
 1717        public void RemoveUnchecked<T0, T1, T2, T3, T4, T5>(int sparseIndexToRemove, T0[] array0, T1[] array1,
 1718            T2[] array2,
 1719            T3[] array3, T4[] array4, T5[] array5)
 01720        {
 01721            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 01722            int newLength = Count - 1;
 01723            int sparseIndexBeingSwapped = DenseArray[newLength];
 1724
 1725            // Swap the entry being removed with the last entry.
 01726            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 01727            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 01728            array0[denseIndexToRemove] = array0[newLength];
 01729            array1[denseIndexToRemove] = array1[newLength];
 01730            array2[denseIndexToRemove] = array2[newLength];
 01731            array3[denseIndexToRemove] = array3[newLength];
 01732            array4[denseIndexToRemove] = array4[newLength];
 01733            array5[denseIndexToRemove] = array5[newLength];
 1734
 1735            // Clear the dense  index, for debugging purposes
 01736            DenseArray[newLength] = -1;
 01737            array0[newLength] = default;
 01738            array1[newLength] = default;
 01739            array2[newLength] = default;
 01740            array3[newLength] = default;
 01741            array4[newLength] = default;
 01742            array5[newLength] = default;
 1743
 1744            // Add the sparse index to the free list.
 01745            SparseArray[sparseIndexToRemove] = FreeIndex;
 01746            FreeIndex = sparseIndexToRemove;
 1747
 01748            Count = newLength;
 01749        }
 1750
 1751        public void RemoveUnchecked<T0, T1, T2, T3, T4, T5, T6>(int sparseIndexToRemove, T0[] array0, T1[] array1,
 1752            T2[] array2, T3[] array3, T4[] array4, T5[] array5, T6[] array6)
 01753        {
 01754            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 01755            int newLength = Count - 1;
 01756            int sparseIndexBeingSwapped = DenseArray[newLength];
 1757
 1758            // Swap the entry being removed with the last entry.
 01759            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 01760            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 01761            array0[denseIndexToRemove] = array0[newLength];
 01762            array1[denseIndexToRemove] = array1[newLength];
 01763            array2[denseIndexToRemove] = array2[newLength];
 01764            array3[denseIndexToRemove] = array3[newLength];
 01765            array4[denseIndexToRemove] = array4[newLength];
 01766            array5[denseIndexToRemove] = array5[newLength];
 01767            array6[denseIndexToRemove] = array6[newLength];
 1768
 1769            // Clear the dense  index, for debugging purposes
 01770            DenseArray[newLength] = -1;
 01771            array0[newLength] = default;
 01772            array1[newLength] = default;
 01773            array2[newLength] = default;
 01774            array3[newLength] = default;
 01775            array4[newLength] = default;
 01776            array5[newLength] = default;
 01777            array6[newLength] = default;
 1778
 1779            // Add the sparse index to the free list.
 01780            SparseArray[sparseIndexToRemove] = FreeIndex;
 01781            FreeIndex = sparseIndexToRemove;
 1782
 01783            Count = newLength;
 01784        }
 1785
 1786        public void RemoveUnchecked<T0, T1, T2, T3, T4, T5, T6, T7>(int sparseIndexToRemove, T0[] array0, T1[] array1,
 1787            T2[] array2, T3[] array3, T4[] array4, T5[] array5, T6[] array6, T7[] array7)
 01788        {
 01789            int denseIndexToRemove = SparseArray[sparseIndexToRemove];
 01790            int newLength = Count - 1;
 01791            int sparseIndexBeingSwapped = DenseArray[newLength];
 1792
 1793            // Swap the entry being removed with the last entry.
 01794            SparseArray[sparseIndexBeingSwapped] = denseIndexToRemove;
 01795            DenseArray[denseIndexToRemove] = sparseIndexBeingSwapped;
 01796            array0[denseIndexToRemove] = array0[newLength];
 01797            array1[denseIndexToRemove] = array1[newLength];
 01798            array2[denseIndexToRemove] = array2[newLength];
 01799            array3[denseIndexToRemove] = array3[newLength];
 01800            array4[denseIndexToRemove] = array4[newLength];
 01801            array5[denseIndexToRemove] = array5[newLength];
 01802            array6[denseIndexToRemove] = array6[newLength];
 01803            array7[denseIndexToRemove] = array7[newLength];
 1804
 1805            // Clear the dense  index, for debugging purposes
 01806            DenseArray[newLength] = -1;
 01807            array0[newLength] = default;
 01808            array1[newLength] = default;
 01809            array2[newLength] = default;
 01810            array3[newLength] = default;
 01811            array4[newLength] = default;
 01812            array5[newLength] = default;
 01813            array6[newLength] = default;
 01814            array7[newLength] = default;
 1815
 1816            // Add the sparse index to the free list.
 01817            SparseArray[sparseIndexToRemove] = FreeIndex;
 01818            FreeIndex = sparseIndexToRemove;
 1819
 01820            Count = newLength;
 01821        }
 1822
 1823        #endregion
 1824    }
 1825}

Coverage by test methods























































Methods/Properties

SparseSet(System.Int32)
SparseSet(System.Int32, System.UInt64[]&)
AddWithExpandCheck(System.Int32, System.Int32&, System.Int32&)
AddWithExpandCheck(System.Int32, System.Int32&, System.Int32&, System.UInt64[]&, System.UInt64&)
AddUnchecked(System.Int32&, System.Int32&)
AddUnchecked(System.Int32&, System.Int32&, System.UInt64[], System.UInt64&)
GetDenseIndexUnchecked(System.Int32)
GetDenseIndexWithBoundsCheck(System.Int32)
GetDenseIndexWithVersionCheck(System.Int32, System.UInt64, System.UInt64[])
GetDenseIndexWithBoundsAndVersionCheck(System.Int32, System.UInt64, System.UInt64[])
RemoveWithBoundsCheck(System.Int32&, System.Int32&, System.Int32&)
RemoveWithVersionCheck(System.Int32, System.UInt64, System.UInt64[], System.Int32&, System.Int32&)
RemoveWithBoundsAndVersionChecks(System.Int32&, System.UInt64, System.UInt64[], System.Int32&, System.Int32&)
RemoveUnchecked(System.Int32)
RemoveUnchecked(System.Int32, System.Int32&, System.Int32&)
RemoveUnchecked(System.Int32, System.UInt64[], System.Int32&, System.Int32&)
RemoveUncheckedFromDenseIndex(System.Int32)
RemoveUncheckedFromDenseIndex(System.Int32, System.UInt64[])
RemoveUncheckedFromDenseIndex(System.Int32, System.Int32&)
RemoveUncheckedFromDenseIndex(System.Int32, System.UInt64[], System.Int32&)
Clear()
Clear(System.UInt64[])
ClearWithVersionArrayReset(System.UInt64[])
Expand(System.Int32)
Expand(System.Int32, System.UInt64[]&)
Reserve(System.Int32)
Reserve(System.Int32, System.UInt64[]&)
AddWithExpandCheck[T0](T0, , System.Int32&, System.Int32)
AddWithExpandCheck[T0, T1](T0, , T1, , System.Int32&, System.Int32)
AddWithExpandCheck[T0, T1, T2](T0, , T1, , T2, , System.Int32&, System.Int32)
AddWithExpandCheck[T0, T1, T2, T3](T0, , T1, , T2, , T3, , System.Int32&, System.Int32)
AddWithExpandCheck[T0, T1, T2, T3, T4](T0, , T1, , T2, , T3, , T4, , System.Int32&, System.Int32)
AddWithExpandCheck[T0, T1, T2, T3, T4, T5](T0, , T1, , T2, , T3, , T4, , T5, , System.Int32&, System.Int32)
AddWithExpandCheck[T0, T1, T2, T3, T4, T5, T6](T0, , T1, , T2, , T3, , T4, , T5, , T6, , System.Int32&, System.Int32)
AddWithExpandCheck[T0, T1, T2, T3, T4, T5, T6, T7](T0, , T1, , T2, , T3, , T4, , T5, , T6, , T7, , System.Int32&, System.Int32)
AddUnchecked[T0](T0, )
AddUnchecked[T0, T1](T0, , T1, )
AddUnchecked[T0, T1, T2](T0, , T1, , T2, )
AddUnchecked[T0, T1, T2, T3](T0, , T1, , T2, , T3, )
AddUnchecked[T0, T1, T2, T3, T4](T0, , T1, , T2, , T3, , T4, )
AddUnchecked[T0, T1, T2, T3, T4, T5](T0, , T1, , T2, , T3, , T4, , T5, )
AddUnchecked[T0, T1, T2, T3, T4, T5, T6](T0, , T1, , T2, , T3, , T4, , T5, , T6, )
AddUnchecked[T0, T1, T2, T3, T4, T5, T6, T7](T0, , T1, , T2, , T3, , T4, , T5, , T6, , T7, )
RemoveUnchecked[T0](System.Int32, )
RemoveUnchecked[T0, T1](System.Int32, , )
RemoveUnchecked[T0, T1, T2](System.Int32, , , )
RemoveUnchecked[T0, T1, T2, T3](System.Int32, , , , )
RemoveUnchecked[T0, T1, T2, T3, T4](System.Int32, , , , , )
RemoveUnchecked[T0, T1, T2, T3, T4, T5](System.Int32, , , , , , )
RemoveUnchecked[T0, T1, T2, T3, T4, T5, T6](System.Int32, , , , , , , )
RemoveUnchecked[T0, T1, T2, T3, T4, T5, T6, T7](System.Int32, , , , , , , , )